package com.weareint.biz.controller;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.weareint.biz.dto.PrinterDTO;
import com.weareint.biz.entity.Printer;
import com.weareint.biz.service.IPrinterService;
import com.weareint.common.TokenProvider;
import com.weareint.common.dto.BatchDeleteByIdDto;
import com.weareint.common.dto.QueryByIdDto;
import com.weareint.common.dto.QueryByPropsWithOprDto;
import com.weareint.common.dto.UpdateByPropsWithOprDto;
import com.weareint.common.vo.Result;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import javax.validation.Valid;
import java.util.Map;

/**
 *
 *
 * <pre>
 *      打印机 前端控制器
 * </pre>
 *
 * @author Auto Generator
 * @date 2021-07-28
 */
@Api(tags = "打印机")
@RestController
@Slf4j
@RequestMapping("/api/printer")
public class PrinterController {

    @Autowired private IPrinterService printerService;

    @Autowired private TokenProvider tokenProvider;

    /**
     *
     *
     * <pre>
     *     保存对象非null属性
     *     curl -X POST -H 'Content-Type: application/json' -d '{}' 'http://localhost:8082/api/printer/save'
     * </pre>
     *
     * @param printerDTO {@link PrinterDTO}
     * @param request {@link HttpServletRequest}
     * @return result saved {@link PrinterDTO}
     */
    @ApiOperation(
            value = "保存对象非null属性",
            notes =
                    "<pre> \n"
                            + "<h3>CURL Example:</h3>\n"
                            + "curl -X POST -H 'Content-Type: application/json' \n"
                            + "-d '{\n"
                            + "\t\"ip\": \"打印机IP地址\", \n"
                            + "\t\"code\": \"打印机编码\", \n"
                            + "\t\"port\": \"打印机端口\", \n"
                            + "\t\"state\": \"状态：0禁用，1启用\", \n"
                            + "\t\"remark\": \"备注\", \n"
                            + "\t\"useType\": \"使用类型：1表示大箱打印机，2表示小盒打印机\", \n"
                            + "\t\"manualPrintEnabled\": \"是否支持手动打印：0表示不支持手动打印，1表示支持手动打印\" \n"
                            + "}' \n"
                            + "'http://localhost:8082/api/printer/save'\n"
                            + "<h3>属性列表</h3>\n"
                            + "<table border='1'>"
                            + "<tr><th>对象属性名</th><th>类型</th><th>说明</th></tr>"
                            + "<tr><td>ip</td><td>String</td><td>打印机IP地址</td></tr>"
                            + "<tr><td>code</td><td>String</td><td>打印机编码</td></tr>"
                            + "<tr><td>port</td><td>Integer</td><td>打印机端口</td></tr>"
                            + "<tr><td>state</td><td>Integer</td><td>状态：0禁用，1启用</td></tr>"
                            + "<tr><td>remark</td><td>String</td><td>备注</td></tr>"
                            + "<tr><td>useType</td><td>Integer</td><td>使用类型：1表示大箱打印机，2表示小盒打印机</td></tr>"
                            + "<tr><td>manualPrintEnabled</td><td>Integer</td><td>是否支持手动打印：0表示不支持手动打印，1表示支持手动打印</td></tr>"
                            + "</table>"
                            + "</pre>")
    @PostMapping("/save")
    public Result<PrinterDTO> save(
            @RequestBody @Valid PrinterDTO printerDTO, HttpServletRequest request) {
        if (log.isDebugEnabled()) {
            log.debug(
                    "printerDTO = "
                            + JSONObject.toJSONString(printerDTO)
                            + ", currentUserId = "
                            + tokenProvider.getUserId(request));
        }
        Printer entity = printerDTO.toEntity();
        printerService.save(entity);
        return Result.ok(entity.toDTO());
    }

    /**
     *
     *
     * <pre>
     *     按条件更新数据
     *     curl -X POST -H 'Content-Type: application/json' \
     *      -d '{"updateProps": [{"prop":"contacts", "type": "string", "val": "yxf002"}, {"prop": "remark", "type": "string", "val": "remark002"}], "wherePropsWithOprs": [{"prop": "code", "type": "string", "val": "test2", "opr": "eq"}]}' \
     *      'http://localhost:8082/api/printer/update'
     * </pre>
     *
     * @param updateByPropsWithOprDto {@link UpdateByPropsWithOprDto}
     * @param request {@link HttpServletRequest}
     * @return result of {@link PrinterDTO}
     */
    @ApiOperation(
            value = "按条件更新指定属性",
            notes =
                    "<pre>\n"
                            + "<h3>CURL Example:</h3> \n"
                            + "curl -X POST -H 'Content-Type: application/json' \n"
                            + "-d '{\n"
                            + "\t\"updateProps\": [ // 需要更新的字段集合\n"
                            + "\t\t{\n"
                            + "\t\t\t\"prop\":\"contacts\", //表字段 \n"
                            + "\t\t\t\"type\": \"string\", // 类型(目前支持string,integer,long,double,date).date只支持yyyy-MM-dd HH:mm:ss格式 \n"
                            + "\t\t\t\"val\": \"yxf001\" // 新的值\n"
                            + "\t\t}, {\n"
                            + "\t\t\t\"prop\": \"remark\", \n"
                            + "\t\t\t\"type\": \"string\", \n"
                            + "\t\t\t\"val\": \"remark002\"\n"
                            + "\t\t}\n"
                            + "\t], \n"
                            + "\t\"wherePropsWithOprs\": [ // 执行更新时的Where条件 \n"
                            + "\t\t{\n"
                            + "\t\t\t\"prop\": \"code\", // 表字段 \n"
                            + "\t\t\t\"type\": \"string\", // 类型(目前支持string,integer,long,double,date).date只支持yyyy-MM-dd HH:mm:ss格式 \n"
                            + "\t\t\t\"val\": \"test2\", // 值\n"
                            + "\t\t\t\"opr\": \"eq\" // 操作符(目前支持eq,lt,le,gt,ge,like,like_left,left_right)\n"
                            + "\t\t}\n"
                            + "\t]\n"
                            + "}' \n"
                            + "'http://localhost:8082/api/printer/update'\n"
                            + "以上相当于执行 update table_name set contacts='yxf001', remark='remark002' where code='test2'\n\n"
                            + "<h3>字段列表</h3>\n"
                            + "<table border='1'>"
                            + "<tr><th>表字段</th><th>类型</th><th>说明</th></tr>"
                            + "<tr><td>ip</td><td>String</td><td>打印机IP地址</td></tr>"
                            + "<tr><td>code</td><td>String</td><td>打印机编码</td></tr>"
                            + "<tr><td>port</td><td>Integer</td><td>打印机端口</td></tr>"
                            + "<tr><td>state</td><td>Integer</td><td>状态：0禁用，1启用</td></tr>"
                            + "<tr><td>remark</td><td>String</td><td>备注</td></tr>"
                            + "<tr><td>use_type</td><td>Integer</td><td>使用类型：1表示大箱打印机，2表示小盒打印机</td></tr>"
                            + "<tr><td>manual_print_enabled</td><td>Integer</td><td>是否支持手动打印：0表示不支持手动打印，1表示支持手动打印</td></tr>"
                            + "</table>"
                            + "</pre>")
    @PostMapping("/update")
    public Result<PrinterDTO> update(
            @RequestBody @Valid UpdateByPropsWithOprDto updateByPropsWithOprDto,
            HttpServletRequest request) {
        if (log.isDebugEnabled()) {
            log.debug(
                    "updateByPropsWithOprDto = "
                            + JSONObject.toJSONString(updateByPropsWithOprDto));
        }
        printerService.update(updateByPropsWithOprDto);
        return Result.ok();
    }

    /**
     *
     *
     * <pre>
     *     按ID批量删除
     *     curl -X POST -H 'Content-Type: application/json' -d '{"ids": [55,56]}' 'http://localhost:8082/api/printer/delete'
     * </pre>
     *
     * @param batchDeleteByIdDto {@link BatchDeleteByIdDto}
     * @param request {@link HttpServletRequest}
     * @return result nothing
     */
    @ApiOperation(
            value = "按ID批量删除",
            notes =
                    "<pre>\n"
                            + "<h3>CURL Example:</h3>\n"
                            + "curl -X POST -H 'Content-Type: application/json' \n"
                            + "-d '{\"ids\": [55,56]}' 'http://localhost:8082/api/printer/delete'\n"
                            + "</pre>")
    @PostMapping("/delete")
    public Result<Void> delete(
            @RequestBody @Valid BatchDeleteByIdDto batchDeleteByIdDto, HttpServletRequest request) {
        if (log.isDebugEnabled()) {
            log.debug(
                    "batchDeleteByIdDto = "
                            + JSONObject.toJSONString(batchDeleteByIdDto)
                            + ", currentUserId = "
                            + tokenProvider.getUserId(request));
        }
        if (null != batchDeleteByIdDto
                && null != batchDeleteByIdDto.getIds()
                && !batchDeleteByIdDto.getIds().isEmpty()) {
            printerService.removeByIds(batchDeleteByIdDto.getIds());
        }
        return Result.ok();
    }

    /**
     *
     *
     * <pre>
     *     按ID查询，并可指定要查询的字段。
     *     curl -X POST -H 'Content-Type: application/json' -d '{ "id": 59 }' 'http://localhost:8082/api/printer/findPropsById'
     *     curl -X POST -H 'Content-Type: application/json' -d '{ "id": 59, "columns": [ "id", "code", "name", "contacts" ] }' 'http://localhost:8082/api/printer/findPropsById'
     * </pre>
     *
     * @param queryByIdDTO {@link QueryByIdDto}
     * @param request {@link HttpServletRequest}
     * @return result of {@link PrinterDTO}
     */
    @ApiOperation(
            value = "按ID查询单条数据，并可指定要查询的字段",
            notes =
                    "<pre>\n"
                            + "<h3>CURL Example:</h3>\n"
                            + "curl -X POST -H 'Content-Type: application/json' \n"
                            + "-d '{\n"
                            + "\t\"id\": 59, \n"
                            + "\t\"columns\": [ // 指定要查询的表字段\n"
                            + "\t\t\"ip\", \n"
                            + "\t\t\"code\", \n"
                            + "\t\t\"port\", \n"
                            + "\t\t\"state\", \n"
                            + "\t\t\"remark\", \n"
                            + "\t\t\"use_type\", \n"
                            + "\t\t\"manual_print_enabled\" \n"
                            + "\t]\n"
                            + "}' 'http://localhost:8082/api/printer/findPropsById'\n\n"
                            + "<h3>字段列表</h3>\n"
                            + "<table border='1'>"
                            + "<tr><th>表字段</th><th>类型</th><th>说明</th></tr>"
                            + "<tr><td>ip</td><td>String</td><td>打印机IP地址</td></tr>"
                            + "<tr><td>code</td><td>String</td><td>打印机编码</td></tr>"
                            + "<tr><td>port</td><td>Integer</td><td>打印机端口</td></tr>"
                            + "<tr><td>state</td><td>Integer</td><td>状态：0禁用，1启用</td></tr>"
                            + "<tr><td>remark</td><td>String</td><td>备注</td></tr>"
                            + "<tr><td>use_type</td><td>Integer</td><td>使用类型：1表示大箱打印机，2表示小盒打印机</td></tr>"
                            + "<tr><td>manual_print_enabled</td><td>Integer</td><td>是否支持手动打印：0表示不支持手动打印，1表示支持手动打印</td></tr>"
                            + "</table>"
                            + "</pre>")
    @PostMapping("/findPropsById")
    public Result<Map<String, Object>> findPropsById(
            @RequestBody @Valid QueryByIdDto queryByIdDTO, HttpServletRequest request) {
        if (log.isDebugEnabled()) {
            log.debug("QueryByIdDto = " + JSONObject.toJSONString(queryByIdDTO));
        }
        return Result.ok(printerService.findPropsById(queryByIdDTO));
    }

    /**
     *
     *
     * <pre>
     *     按条件分页查询指定字段
     *     curl -X POST "http://localhost:8082/api/printer/findPropsByPage" -H "Content-Type: application/json" -d "{}"
     *
     *     curl -X POST -H 'Content-Type: application/json' \
     *      -d '{ "columns": ["id", "code", "name"], "page": 2, "size": 20, "wherePropsWithOprs": [ { "prop": "code", "type": "string", "opr": "like", "val": "te" } ], "orderByProps": [ { "prop": "code", "desc": true }, {"prop": "id", "desc": false} ] }' \
     *      'http://localhost:8082/api/printer/findPropsByPage'
     * </pre>
     *
     * @param queryByPropsWithOprDto {@link QueryByPropsWithOprDto}
     * @param request {@link HttpServletRequest}
     * @return result of {@link PrinterDTO}
     */
    @ApiOperation(
            value = "按条件分页查询指定字段",
            notes =
                    "<pre>\n"
                            + "<h3>CURL Example:</h3>\n"
                            + "curl -X POST -H 'Content-Type: application/json' \n"
                            + "-d '{\n"
                            + "\t\"columns\": [\"id\", \"code\", \"name\"], // 指定要查询的数据表字段，默认查询全部\n"
                            + "\t\"page\": 2,  // 页码，从1开始\n"
                            + "\t\"size\": 20,  // 每页记录数，最大不超过10000\n"
                            + "\t\"wherePropsWithOprs\": [ // 查询条件\n"
                            + "\t\t{\n"
                            + "\t\t\t\"prop\": \"code\", \n"
                            + "\t\t\t\"type\": \"string\", // 类型(目前支持string,integer,long,double,date).date只支持yyyy-MM-dd HH:mm:ss格式 \n"
                            + "\t\t\t\"opr\": \"like\", // 操作符(目前支持eq,lt,le,gt,ge,like,like_left,left_right) \n"
                            + "\t\t\t\"val\": \"te\" \n"
                            + "\t\t}\n"
                            + "\t], \n"
                            + "\t\"orderByProps\": [ // 添加排序\n"
                            + "\t\t{ \n"
                            + "\t\t\t\"prop\": \"code\", // 参与排序的数据表字段\n"
                            + "\t\t\t\"desc\": true \n"
                            + "\t\t}, {\n"
                            + "\t\t\t\"prop\": \"id\", \n"
                            + "\t\t\t\"desc\": false\n"
                            + "\t\t}\n"
                            + "\t]\n"
                            + "}'\n"
                            + "'http://localhost:8082/api/printer/findPropsByPage'\n\n"
                            + "<h3>字段列表</h3>\n"
                            + "<table border='1'>"
                            + "<tr><th>表字段</th><th>类型</th><th>说明</th></tr>"
                            + "<tr><td>ip</td><td>String</td><td>打印机IP地址</td></tr>"
                            + "<tr><td>code</td><td>String</td><td>打印机编码</td></tr>"
                            + "<tr><td>port</td><td>Integer</td><td>打印机端口</td></tr>"
                            + "<tr><td>state</td><td>Integer</td><td>状态：0禁用，1启用</td></tr>"
                            + "<tr><td>remark</td><td>String</td><td>备注</td></tr>"
                            + "<tr><td>use_type</td><td>Integer</td><td>使用类型：1表示大箱打印机，2表示小盒打印机</td></tr>"
                            + "<tr><td>manual_print_enabled</td><td>Integer</td><td>是否支持手动打印：0表示不支持手动打印，1表示支持手动打印</td></tr>"
                            + "</table>"
                            + "</pre>")
    @PostMapping("/findPropsByPage")
    public Result<Page<Map<String, Object>>> findPropsByPage(
            @RequestBody @Valid QueryByPropsWithOprDto queryByPropsWithOprDto,
            HttpServletRequest request) {
        if (log.isDebugEnabled()) {
            log.debug(
                    "queryByPropsWithOprDto = " + JSONObject.toJSONString(queryByPropsWithOprDto));
        }
        return Result.ok(printerService.findPropsByPage(queryByPropsWithOprDto));
    }
}
